package com.miukoo.aikao.admin.security;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.miukoo.aikao.admin.service.JwtUserRedisService;
import com.miukoo.aikao.core.dtos.ApiResult;
import com.miukoo.aikao.core.enums.ApiError;
import com.miukoo.aikao.core.pojos.SecurityUser;
import com.miukoo.aikao.core.utils.ApiUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.web.authentication.AuthenticationFailureHandler;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;
import org.springframework.stereotype.Component;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * @Author miukoo<miukoo@126.com>
 * @Date 2020/11/22  
 * @Version 1.0
 */
@Component
public class SecurityUserLoginHandler implements AuthenticationFailureHandler, AuthenticationSuccessHandler {

    @Autowired
    private JwtUserRedisService jwtUserRedisService;
    @Autowired
    ObjectMapper objectMapper;

    @Override
    public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException {
        ApiResult<String> failure = ApiUtils.failure(ApiError.ERROR_20010002, exception.getMessage());
        response.setContentType(MediaType.APPLICATION_JSON_UTF8_VALUE);
        String result = objectMapper.writeValueAsString(failure);
        response.setStatus(HttpStatus.OK.value());
        response.getOutputStream().write(result.getBytes());
    }

    @Override
    public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException {
        String jwtid = buildJwtUset2Redis(authentication);
        response.setHeader("token", jwtid);
        ApiResult<String> success = ApiUtils.success(jwtid);
        String result = objectMapper.writeValueAsString(success);
        response.setContentType(MediaType.APPLICATION_JSON_UTF8_VALUE);
        response.setStatus(HttpStatus.OK.value());
        response.getOutputStream().write(result.getBytes());
    }

    /**
     * 构造一个用户信息，存储到Redis中
     * @param authentication
     * @return
     * @throws JsonProcessingException
     */
    public String  buildJwtUset2Redis(Authentication authentication) throws JsonProcessingException {
        SecurityUserDto jwtUser = (SecurityUserDto) authentication.getPrincipal();
        SecurityUser user = new SecurityUser();
        user.setId(jwtUser.getUserId());
        user.setUserName(jwtUser.getUsername());
        if(authentication.getAuthorities()!=null) {
            user.setAuthorities(objectMapper.writeValueAsString(authentication.getAuthorities()));
        }
        String jwtid = jwtUserRedisService.saveUser(user);
        return jwtid;
    }


}
